package service;

import domain.Field;
import freemarker.template.Configuration;
import org.apache.commons.lang3.text.WordUtils;

import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.sql.*;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Properties;

/**
 * Created by Greg.Chen on 2015/3/18.
 */
public class GenerateContext {

    public GenerateContext() throws SQLException {


        Properties properties = getProp();

        projectName = properties.getProperty("projectName");

        tableName = properties.getProperty("tableName");
        domainPackage = generatePackageName("domain");
        daoPackage = generatePackageName("dao");
        daoImplPackage = generatePackageName("dao") + ".impl";
        servicePackage = generatePackageName("service");
        serviceImplPackage = generatePackageName("service") + ".impl";
        controllerPackage = generatePackageName("controller");
        viewPackage = generatePackageName("view.domain");
        requestPackage = generatePackageName("request");

        path = properties.getProperty("outputPath");

        projectPath = properties.getProperty("projectPath") + "/src/main";

        File file = new File(path);
        if(!file.exists())
            file.mkdirs();

        domainPath = projectPath + "/java/" + domainPackage.replace(".","/") + "/" + WordUtils.capitalize(tableName) + ".java";
        daoPath = projectPath + "/java/" + daoPackage.replace(".","/") + "/" + WordUtils.capitalize(tableName) + "Dao.java";
        daoImplPath = projectPath + "/java/" + daoImplPackage.replace(".","/") + "/" + WordUtils.capitalize(tableName) + "DaoImpl.java";
        servicePath =  projectPath + "/java/" + servicePackage.replace(".","/") + "/" + WordUtils.capitalize(tableName) + "Service.java";
        serviceImplPath =  projectPath + "/java/" + serviceImplPackage.replace(".","/") + "/" + WordUtils.capitalize(tableName) + "ServiceImpl.java";
        xmlPath =  projectPath + "/resources/mapper/" + tableName + ".xml";
        mngControllerPath = path + WordUtils.capitalize(tableName) + "MngController.java";
        controllerPath = path + WordUtils.capitalize(tableName) + "Controller.java";
        mngHtmlPath = path + tableName + "Mng.html";
        mngFormHtmlPath = path + tableName + "Form.html";
        mngJSPath = path + tableName + "MngCtrl.js";

        viewPath = path + WordUtils.capitalize(tableName) + "ListView.java";
        requestSearchFormPath = path + WordUtils.capitalize(tableName) + "SearchForm.java";
        requestAddFormPath = path + WordUtils.capitalize(tableName) + "AddForm.java";
        //Freemarker configuration object
        cfg = new Configuration();

        getColNames();
    }

    private String generatePackageName(String packageName){
        return "com." + projectName + "." + packageName;
    }

    private void getColNames()  throws SQLException {
        List<Field> fields = new ArrayList<Field>();
        HashSet<String> columnClassNames = new HashSet<String>();

        Connection conn  = DataSourceUtils.getConn();
        Statement st = conn.createStatement();

        String sql = "select * from `" + tableName + "`";
        ResultSet rs = st.executeQuery(sql);

        ResultSetMetaData rsmd = rs.getMetaData();

        int cols = rsmd.getColumnCount();

        for(int i=0;i<cols;i++){
            String colName = rsmd.getColumnName(i + 1);
            String colType = rsmd.getColumnClassName(i + 1);

            if(colType.equals("java.math.BigDecimal")){
                colType = "java.lang.Double";
            }

            columnClassNames.add(colType);

            colType = colType.substring(colType.lastIndexOf('.') + 1);



            if(colName.equalsIgnoreCase("createTime") || colName.equalsIgnoreCase("updateTime"))
                continue;


            fields.add(new Field(colName, colType, rsmd.isAutoIncrement(i+1)));
        }

        System.out.println("列名:" + fields);
        System.out.println("列类型:" + columnClassNames);

        this.fields =fields;
        this.columnClassNames = columnClassNames;

    }

    public Properties getProp(){
        Properties properties = new Properties();
        InputStream inputStream = GenerateContext.class.getClassLoader().getResourceAsStream("config.properties");
        if(inputStream != null){
            try {
                properties.load(inputStream);
            } catch (IOException e) {
                e.printStackTrace();
            }
        }

        return  properties;
    }

    private List<Field> fields;
    private HashSet<String> columnClassNames;
    private Configuration cfg;

    private String tableName;
    private String path;
    private String domainPath;
    private String daoPath;
    private String daoImplPath;
    private String servicePath;
    private String serviceImplPath;
    private String xmlPath;
    private String domainPackage;
    private String daoPackage;
    private String daoImplPackage;
    private String servicePackage;
    private String serviceImplPackage;
    private String mngControllerPath;
    private String controllerPackage;
    private String controllerPath;
    private String mngHtmlPath;
    private String mngFormHtmlPath;
    private String mngJSPath;
    private String viewPackage;
    private String requestPackage;
    private String viewPath;
    private String requestSearchFormPath;
    private String requestAddFormPath;

    private String projectPath;

    private String projectName;

    public String getMngJSPath() {
        return mngJSPath;
    }

    public void setMngJSPath(String mngJSPath) {
        this.mngJSPath = mngJSPath;
    }

    public String getPath() {
        return path;
    }

    public void setPath(String path) {
        this.path = path;
    }

    public String getDomainPath() {
        return domainPath;
    }

    public void setDomainPath(String domainPath) {
        this.domainPath = domainPath;
    }

    public String getDaoPath() {
        return daoPath;
    }

    public void setDaoPath(String daoPath) {
        this.daoPath = daoPath;
    }

    public String getDaoImplPath() {

        return daoImplPath;
    }

    public void setDaoImplPath(String daoImplPath) {
        this.daoImplPath = daoImplPath;
    }

    public String getServicePath() {
        return servicePath;
    }

    public void setServicePath(String servicePath) {
        this.servicePath = servicePath;
    }

    public String getServiceImplPath() {
        return serviceImplPath;
    }

    public void setServiceImplPath(String serviceImplPath) {
        this.serviceImplPath = serviceImplPath;
    }

    public String getDomainPackage() {
        return domainPackage;
    }

    public void setDomainPackage(String domainPackage) {
        this.domainPackage = domainPackage;
    }

    public String getDaoPackage() {
        return daoPackage;
    }

    public void setDaoPackage(String daoPackage) {
        this.daoPackage = daoPackage;
    }

    public String getDaoImplPackage() {
        return daoImplPackage;
    }

    public void setDaoImplPackage(String daoImplPackage) {
        this.daoImplPackage = daoImplPackage;
    }

    public String getServicePackage() {
        return servicePackage;
    }

    public void setServicePackage(String servicePackage) {
        this.servicePackage = servicePackage;
    }

    public String getServiceImplPackage() {
        return serviceImplPackage;
    }

    public void setServiceImplPackage(String serviceImplPackage) {
        this.serviceImplPackage = serviceImplPackage;
    }

    public String getXmlPath() {
        return xmlPath;
    }


    public String getMngControllerPath() {
        return mngControllerPath;
    }

    public void setMngControllerPath(String mngControllerPath) {
        this.mngControllerPath = mngControllerPath;
    }

    public String getControllerPackage() {
        return controllerPackage;
    }

    public void setControllerPackage(String controllerPackage) {
        this.controllerPackage = controllerPackage;
    }

    public void setXmlPath(String xmlPath) {
        this.xmlPath = xmlPath;
    }

    public List<Field> getFields() {
        return fields;
    }

    public void setFields(List<Field> fields) {
        this.fields = fields;
    }

    public HashSet<String> getColumnClassNames() {
        return columnClassNames;
    }

    public void setColumnClassNames(HashSet<String> columnClassNames) {
        this.columnClassNames = columnClassNames;
    }

    public Configuration getCfg() {
        return cfg;
    }

    public void setCfg(Configuration cfg) {
        this.cfg = cfg;
    }

    public String getTableName() {
        return tableName;
    }

    public void setTableName(String tableName) {
        this.tableName = tableName;
    }

    public String getControllerPath() {
        return controllerPath;
    }

    public void setControllerPath(String controllerPath) {
        this.controllerPath = controllerPath;
    }

    public String getMngHtmlPath() {
        return mngHtmlPath;
    }

    public void setMngHtmlPath(String mngHtmlPath) {
        this.mngHtmlPath = mngHtmlPath;
    }

    public String getMngFormHtmlPath() {
        return mngFormHtmlPath;
    }

    public void setMngFormHtmlPath(String mngFormHtmlPath) {
        this.mngFormHtmlPath = mngFormHtmlPath;
    }

    public String getViewPackage() {
        return viewPackage;
    }

    public void setViewPackage(String viewPackage) {
        this.viewPackage = viewPackage;
    }

    public String getRequestPackage() {
        return requestPackage;
    }

    public void setRequestPackage(String requestPackage) {
        this.requestPackage = requestPackage;
    }

    public String getViewPath() {
        return viewPath;
    }

    public void setViewPath(String viewPath) {
        this.viewPath = viewPath;
    }

    public String getRequestSearchFormPath() {
        return requestSearchFormPath;
    }

    public void setRequestSearchFormPath(String requestSearchFormPath) {
        this.requestSearchFormPath = requestSearchFormPath;
    }

    public String getRequestAddFormPath() {
        return requestAddFormPath;
    }

    public void setRequestAddFormPath(String requestAddFormPath) {
        this.requestAddFormPath = requestAddFormPath;
    }

    public String getProjectPath() {
        return projectPath;
    }

    public void setProjectPath(String projectPath) {
        this.projectPath = projectPath;
    }
}
